/*******************************************************************************
 * Copyright (c) 2011 TXT e-solutions SpA
 * All rights reserved. This program and the accompanying materials
 * are made available under the terms of the Eclipse Public License v1.0
 * which accompanies this distribution, and is available at
 * http://www.eclipse.org/legal/epl-v10.html
 *
 * This work was performed within the IoT_at_Work Project
 * and partially funded by the European Commission's
 * 7th Framework Programme under the research area ICT-2009.1.3
 * Internet of Things and enterprise environments.
 *
 *
 * Authors:
 *     Cristoforo Seccia (TXT e-solutions SpA)
 *
 * Contributors:
 *      Domenico Rotondi (TXT e-solutions SpA)
 *******************************************************************************/
package it.txt.access.capability.demo.soap.client.view;

import it.txt.access.capability.commons.schema.validation.CapabilitySchemaValidationHandlerException;
import it.txt.access.capability.factory.CapabilitySchemaFactoryException;
import it.txt.access.capability.factory.CapabilitySchemaFactory;
import it.txt.access.capability.demo.schema.CapabilityRequestType;
import it.txt.access.capability.demo.schema.factory.CapabilityDemoSchemaFactory;
import it.txt.access.capability.demo.schema.factory.CapabilityDemoSchemaFactoryException;
import it.txt.access.capability.demo.soap.client.view.model.ServiceRequestCapabilityModel;
import it.txt.access.capability.demo.soap.client.view.model.UserKeystoreDataModel;
import it.txt.access.capability.schema.AccessRightType;
import it.txt.access.capability.schema.AccessRightsCapabilityType;
import it.txt.access.capability.verifier.security.KeystoreHelper;
import it.txt.access.capability.verifier.security.KeystoreSecurityException;
import it.txt.access.capability.verifier.security.KeystoreSignature;
import java.io.File;
import java.security.GeneralSecurityException;
import java.security.KeyStore;
import java.security.KeyStoreException;
import java.util.ArrayList;
import java.util.List;
import org.w3c.dom.Document;
import org.w3c.dom.Element;

/**
 *
 * @author Cristoforo Seccia (TXT e-solutions SpA)
 */
public class ClientGUIControllerHelper {

    private static KeystoreSignature.CertificateKeyValues userDataKeystoreSignatureCertKeyValues;
    private static AccessRightsCapabilityType userAccessRightsCapabilityType;
    private static KeystoreSignature userDataKeystoreSignature;

    protected static ServiceRequestCapabilityModel loadUserCapability(File capabilityFile) throws CapabilitySchemaFactoryException, CapabilitySchemaValidationHandlerException {
        userAccessRightsCapabilityType = CapabilitySchemaFactory.getAccessRightsCapabilityFromFile(capabilityFile);
        ServiceRequestCapabilityModel userCapabilityModel = new ServiceRequestCapabilityModel();
        String policyResourceID = userAccessRightsCapabilityType.getResourceID();
        userCapabilityModel.setResourceID(policyResourceID);
        String capabilityIDString = userAccessRightsCapabilityType.getAccessRightsCapabilityID();
        userCapabilityModel.setCapabilityID(capabilityIDString);
        List<AccessRightType> arts = userAccessRightsCapabilityType.getAccessRights().getAccessRight();
        List<String> operatrions = new ArrayList<String>();
        for (AccessRightType accessRightType : arts) {
            operatrions.add(accessRightType.getPermittedAction().getValue());
        }
        userCapabilityModel.setOperations(operatrions);
        userCapabilityModel.setCapabilityPath(capabilityFile.getAbsolutePath());
        return userCapabilityModel;
    }

    protected static void recoverUserDataX509Certificate(final UserKeystoreDataModel model) throws ClientGUIHelperException {

        java.security.cert.X509Certificate x509Certificate = null;
        KeyStore keyStore = null;
        String alias = null;
        try {
            //Recover the Keystore.
            keyStore = KeystoreHelper.getKeyStore(model.getKeystorePath(), model.getKeystorePsw());
            //Recover the certificate from the Keystore
            x509Certificate = KeystoreHelper.getX509CertificateByIssuer(keyStore, model.getUserID());
            //Check if we have found a certificate with the provided issuer.
            if (x509Certificate != null) {
                try {
                    //Recover the alias of the certificate
                    alias = KeystoreHelper.getAlias(keyStore, x509Certificate);
                    //Recover the private key of the.
                    userDataKeystoreSignature = new KeystoreSignature();
                    userDataKeystoreSignatureCertKeyValues =
                            userDataKeystoreSignature.getCertificateKeyValues(
                            model.getKeystorePath(), model.getPrivateKeyPsw(),
                            alias, model.getPrivateKeyPsw());
                } catch (KeyStoreException ex) {
                    throw new ClientGUIHelperException("Cannot recover the alias of the certificate.");
                } catch (KeystoreSecurityException ex) {
                    throw new ClientGUIHelperException("Error while recovering certificate private key.");
                }
            } else {
                throw new ClientGUIHelperException("Cannot find a certificate by using: " + model.getUserID());
            }
        } catch (KeystoreSecurityException ex) {
            throw new ClientGUIHelperException(ex.getMessage());
        } catch (GeneralSecurityException ex) {
            throw new ClientGUIHelperException("Error while searching for certificate into keystore.");
        }
    }

    protected static Element createSignedCapabilityRequest(String resourceID, String operation) throws ClientGUIHelperException {

        if (userAccessRightsCapabilityType == null) {
            throw new ClientGUIHelperException("Undefined User Capability.");
        }
        if (userDataKeystoreSignature == null) {
            throw new ClientGUIHelperException("Undefined User Keystore File.");
        }
        if (userDataKeystoreSignatureCertKeyValues == null) {
            throw new ClientGUIHelperException("Undefined User X509 Certificate.");
        }

        try {

            CapabilityRequestType userCapabilityRequest =
                    CapabilityDemoSchemaFactory.createCapabilityRequest(
                    operation, resourceID, userAccessRightsCapabilityType);

            Document userCapabilityrequestDocument =
                    CapabilityDemoSchemaFactory.getFragmentCapabilityRequestToDocument(userCapabilityRequest);

            Element userCapabilityrequestDocumentElement = 
                    userCapabilityrequestDocument.getDocumentElement();
            
            userDataKeystoreSignature.signElementObject(
                    userCapabilityrequestDocumentElement,
                    userDataKeystoreSignatureCertKeyValues, "CapabilityRequestID");

            return userCapabilityrequestDocumentElement;
        }
        catch  (CapabilityDemoSchemaFactoryException ex) {
            throw new ClientGUIHelperException(ex.getMessage(), ex);
        }
        catch (KeystoreSecurityException ex) {
            throw new ClientGUIHelperException(ex.getMessage(), ex);
        }
    }
}
